package agu.misc;

import android.content.Intent;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import androidx.annotation.Nullable;
import androidx.core.util.Supplier;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentActivity;
import androidx.fragment.app.FragmentManager;
import androidx.lifecycle.LifecycleOwner;

/**
 * @see #startActivityForResult(Supplier, ActivityResultCallback) startActivityForResult
 * @see #runOnResumeOrNow(Runnable) runOnResumeOrNow
 */
public class ActivityUtil extends Fragment
{

    public static ActivityUtil with(LifecycleOwner owner){
        return with(owner, ActivityUtil.class);
    }

    public static <F extends Fragment> F with(LifecycleOwner owner, Class<F> type){
        FragmentManager manager = null;
        if(owner instanceof FragmentActivity){
            manager = ((FragmentActivity)owner).getSupportFragmentManager();
        }else if(owner instanceof Fragment){
            manager = ((Fragment)owner).getFragmentManager();
        }

        String tag = type.getName();

        Fragment f = manager == null? null: manager.findFragmentByTag(tag);

        if(f == null){
            try{
                f = type.newInstance();

                if(manager != null){
                    manager.beginTransaction().add(f, tag).commitNowAllowingStateLoss();
                }
            }catch(Exception ex){
                ex.printStackTrace();
            }
        }

        //noinspection unchecked
        return (F)f;
    }

    //<editor-fold desc="startActivityForResult">
    public interface ActivityResultCallback
    {
        void onActivityResult(int resultCode, Intent data);
    }

    final Map<Object, ActivityResultCallback> resultCallbacks = new LinkedHashMap<>();
    int requestCode = 0;

    /**
     * @see android.app.Activity#startActivityForResult(Intent, int)
     */
    public void startActivityForResult(Supplier<Intent> intent, ActivityResultCallback callback){
        startActivityForResult(intent.get(), callback);
    }

    /**
     * @see android.app.Activity#startActivityForResult(Intent, int)
     */
    public void startActivityForResult(Intent intent, ActivityResultCallback callback){
        requestCode = 1 + requestCode % 0xFFFF;
        resultCallbacks.put(requestCode, callback);
        startActivityForResult(intent, requestCode);
    }

    @Override
    public void onActivityResult(int requestCode, int resultCode, @Nullable Intent data){
        ActivityResultCallback callback = resultCallbacks.remove(requestCode);
        if(callback != null){
            callback.onActivityResult(resultCode, data);
            return;
        }
        super.onActivityResult(requestCode, resultCode, data);
    }
    //</editor-fold>

    //<editor-fold desc="runOnResumeOrNow">
    List<Runnable> resumeActions = new ArrayList<>();

    /**
     * 在界面恢复可见或已可见时运行一次action
     */
    public void runOnResumeOrNow(Runnable action){
        if(resumeActions.contains(null)) resumeActions.add(action);
        else action.run();
    }

    @Override
    public void onResume(){
        super.onResume();
        for(Runnable action: resumeActions){
            if(action != null) action.run();
        }
        resumeActions.clear();
    }

    @Override
    public void onPause(){
        super.onPause();
        resumeActions.add(null);
    }
    //</editor-fold>

}
